package com.cskaoyan.service.impl;

import com.cskaoyan.mapper.*;
import com.cskaoyan.model.*;
import com.cskaoyan.model.System;
import com.cskaoyan.model.bo.*;
import com.cskaoyan.model.vo.DataVO;
import com.cskaoyan.model.vo.OrderDetialVO;
import com.cskaoyan.model.vo.WxOrderListVO;
import com.cskaoyan.service.OrderService;
import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
import org.apache.shiro.SecurityUtils;
import org.apache.shiro.subject.Subject;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.servlet.http.HttpSession;
import java.math.BigDecimal;
import java.security.Security;
import java.text.SimpleDateFormat;
import java.util.*;

/**
 * @ClassName: OrderServiceImpl
 * @Description: TODO 订单模块service实现类,完成具体业务逻辑
 * @Author:zk
 * @Date: 2022/5/5 20:15
 * @Version: 1.0
 **/
@Transactional
@Service
public class OrderServiceImpl implements OrderService {
    @Autowired
    OrderMapper orderMapper;
    @Autowired
    OrderGoodsMapper orderGoodsMapper;
    @Autowired
    UserMapper userMapper;
    @Autowired
    CommentMapper commentMapper;
    @Autowired
    AddressMapper addressMapper;
    @Autowired
    CartMapper cartMapper;
    @Autowired
    RegionMapper regionMapper;
    @Autowired
    SystemMapper systemMapper;
    @Autowired
    CouponMapper couponMapper;
    @Autowired
    CouponUserMapper couponUserMapper;
    @Autowired
    GoodsProductMapper goodsProductMapper;

    /**
     * @author: zhoukang
     * @description: TODO 查询订单列表
     * @date: 2022/5/6 23:08
     */
    @Override
    public DataVO<Order> query(BaseParamBO param, OrderListBO orderListBO) {
        Integer limit = param.getLimit();
        String sort = param.getSort();
        Integer page = param.getPage();
        String order = param.getOrder();
        //分页
        PageHelper.startPage(page, limit);
        //执行查询:deleted逻辑删除为false的订单
        OrderExample orderExample = new OrderExample();
        orderExample.setOrderByClause(sort + " " + order);

        OrderExample.Criteria criteria = orderExample.createCriteria();

        if (!(orderListBO.getOrderStatusArray() == null)) {
            criteria.andOrderStatusIn(Arrays.asList(orderListBO.getOrderStatusArray()));
        }
        if (!(orderListBO.getStart() == null)) {
            criteria.andPayTimeBetween(orderListBO.getStart(), orderListBO.getEnd());
        }
        if (!(orderListBO.getUserId() == null)) {
            criteria.andUserIdEqualTo(orderListBO.getUserId());
        }
        if (!(orderListBO.getOrderSn() == null)) {
            criteria.andOrderSnLike("%" + orderListBO.getOrderSn() + "%");
        }
        criteria.andDeletedEqualTo(false);
        List<Order> list = orderMapper.selectByExample(orderExample);
        //根据list获取total和pages
        PageInfo<Order> pageInfo = new PageInfo<>(list);
        long total = pageInfo.getTotal();
        int pages = pageInfo.getPages();
        return DataVO.data(total, pages, limit, page, list);
    }

    /**
     * @author: zhoukang
     * @description: TODO 查询订单详情
     * @date: 2022/5/7 9:00
     */
    @Override
    public OrderDetailBO queryOrderDetail(Integer id) {
        Order order = orderMapper.selectByPrimaryKey(id);

        OrderGoodsExample orderGoodsExample = new OrderGoodsExample();
        OrderGoodsExample.Criteria criteria = orderGoodsExample.createCriteria();
        criteria.andOrderIdEqualTo(id);
        criteria.andDeletedEqualTo(false);
        List<OrderGoods> orderGoods = orderGoodsMapper.selectByExample(orderGoodsExample);

        Integer userId = order.getUserId();
        User user = userMapper.selectByPrimaryKey(userId);
        return new OrderDetailBO(order, orderGoods, user);
    }

    /**
     * @author: zhoukang
     * @description: TODO 订单退款
     * @date: 2022/5/7 9:01
     */
    @Override
    public void updateRefund(Map orderData) {
        Order order = new Order();
        order.setId((Integer) orderData.get("orderId"));
        order.setRefundAmount((BigDecimal) orderData.get("refoundMoney"));
        order.setOrderStatus((short) 203);
        order.setRefundTime(new Date());
        order.setUpdateTime(new Date());
        orderMapper.updateByPrimaryKeySelective(order);
    }

    /**
     * @author: zhoukang
     * @description: TODO 订单发货
     * @date: 2022/5/7 9:04
     */
    @Override
    public void updateShip(Map orderData) {
        Order order = new Order();
        order.setId((Integer) orderData.get("orderId"));
        order.setShipChannel((String) orderData.get("shipChannel"));
        order.setShipSn((String) orderData.get("shipSn"));
        order.setOrderStatus((short) 301);
        order.setShipTime(new Date());
        order.setUpdateTime(new Date());
        orderMapper.updateByPrimaryKeySelective(order);
    }

    /**
     * @author: zhoukang
     * @description: TODO 订单逻辑删除
     * @date: 2022/5/7 9:12
     */
    @Override
    public boolean delete(Map orderId) {
        Order order = new Order();
        order.setId((Integer) orderId.get("orderId"));
        order.setUpdateTime(new Date());
        Order orderDeleted = orderMapper.selectByPrimaryKey((Integer) orderId.get("orderId"));
        Short orderStatus = orderDeleted.getOrderStatus();
        if (orderStatus == (short) 101 || orderStatus == ((short) 102) || orderStatus == ((short) 103)) {
            //逻辑删除
            order.setDeleted(true);
            orderMapper.updateByPrimaryKeySelective(order);
            return true;
        }
        return false;
    }

    @Override
    /**
     * @author: huzhouming
     * @description: 根据showType分类查询订单
     * @date: 2022/5/9
     * @param param
     * @return com.cskaoyan.model.vo.DataVO
     */
    public DataVO queryWxOrderList(WxOrderBO param) {
        Integer limit = param.getLimit();
        Integer showType = param.getShowType();
        Integer page = param.getPage();
        //分页
        PageHelper.startPage(page, limit);
        //执行查询:根据showType分类查询订单
        OrderExample orderExample = new OrderExample();
        OrderExample.Criteria criteria = orderExample.createCriteria();
        List<WxOrderListVO> list = null;
        switch (showType) {
            case 0:
                list = orderMapper.selectAll();
                for (WxOrderListVO wxOrderListVO : list) {
                    List<GoodsList> goodsLists = orderGoodsMapper.selectOrderGoodsByGoodsId(wxOrderListVO.getId());
                    wxOrderListVO.setGoodsList(goodsLists);
                }
                break;
            case 1:
                list = orderMapper.selectOrderListByOrderStatus((short) 101);
                for (WxOrderListVO wxOrderListVO : list) {
                    List<GoodsList> goodsLists = orderGoodsMapper.selectOrderGoodsByGoodsId(wxOrderListVO.getId());
                    wxOrderListVO.setGoodsList(goodsLists);
                }
                break;
            case 2:
                list = orderMapper.selectOrderListByOrderStatus((short) 201);
                for (WxOrderListVO wxOrderListVO : list) {
                    List<GoodsList> goodsLists = orderGoodsMapper.selectOrderGoodsByGoodsId(wxOrderListVO.getId());
                    wxOrderListVO.setGoodsList(goodsLists);
                }
                break;
            case 3:
                list = orderMapper.selectOrderListByOrderStatus((short) 301);
                for (WxOrderListVO wxOrderListVO : list) {
                    List<GoodsList> goodsLists = orderGoodsMapper.selectOrderGoodsByGoodsId(wxOrderListVO.getId());
                    wxOrderListVO.setGoodsList(goodsLists);
                }
                break;
            case 4:
                list = orderMapper.selectOrderListByOrderStatus((short) 401, (short) 402);
                for (WxOrderListVO wxOrderListVO : list) {
                    List<GoodsList> goodsLists = orderGoodsMapper.selectOrderGoodsByGoodsId(wxOrderListVO.getId());
                    wxOrderListVO.setGoodsList(goodsLists);
                }
                break;
        }

        //根据list获取total和pages
        PageInfo<WxOrderListVO> pageInfo = new PageInfo<>(list);
        long total = pageInfo.getTotal();
        int pages = pageInfo.getPages();
        return DataVO.data(total, pages, limit, page, list);
    }

    @Override
    /**
     * @author: huzhouming
     * @description: 进入订单细节
     * @date: 2022/5/9
     * @param orderId
     * @return com.cskaoyan.model.vo.OrderDetialVO
     */
    public OrderDetialVO selectDetail(Integer orderId) {
        OrderInfo orderInfo = orderMapper.selectOrderInfoByPrimaryKey(orderId);
        List<OrderGoods> list = orderGoodsMapper.selectOrderGoodsByOrderId(orderId);
        OrderDetialVO orderDetialVO = new OrderDetialVO();
        orderDetialVO.setOrderGoods(list);
        orderDetialVO.setOrderInfo(orderInfo);
        return orderDetialVO;
    }

    @Override
    /**
     * @author: huzhouming
     * @description: 用户申请退款
     * @date: 2022/5/9
     * @param map
     * @return void
     */
    public void updateUserRefund(Map map) {
        Order order = new Order();
        order.setId((Integer) map.get("orderId"));
        order.setOrderStatus((short) 202);
        order.setUpdateTime(new Date());
        orderMapper.updateByPrimaryKeySelective(order);
    }

    @Override
    /**
     * @author: huzhouming
     * @description: 用户取消订单
     * @date: 2022/5/9
     * @param map
     * @return void
     */
    public void updateUserCancel(Map map) {
        //修改订单状态
        Order order = new Order();
        order.setId((Integer) map.get("orderId"));
        order.setOrderStatus((short) 102);
        order.setUpdateTime(new Date());
        orderMapper.updateByPrimaryKeySelective(order);
        //把库存加上去
        List<OrderGoods> orderGoods = orderGoodsMapper.selectOrderGoodsByOrderId(order.getId());
        for (OrderGoods orderGoods1 : orderGoods) {
            goodsProductMapper.updateNumberById((int) orderGoods1.getNumber(), orderGoods1.getProductId());
        }
    }

    @Override
    /**
     * @author: huzhouming
     * @description: 用户删除订单
     * @date: 2022/5/9
     * @param map
     * @return void
     */
    public void updateUserDelete(Map map) {
        Order order = new Order();
        order.setId((Integer) map.get("orderId"));
        order.setDeleted(true);
        order.setUpdateTime(new Date());
        orderMapper.updateByPrimaryKeySelective(order);
    }

    @Override
    /**
     * @author: huzhouming
     * @description: 用户确认收货
     * @date: 2022/5/9
     * @param map
     * @return void
     */
    public void updateUserConfirm(Map map) {
        Order order = new Order();
        order.setId((Integer) map.get("orderId"));
        order.setOrderStatus((short) 401);
        order.setUpdateTime(new Date());
        //获取当前用户信息
        Subject subject = SecurityUtils.getSubject();
        String username = (String) subject.getPrincipals().getPrimaryPrincipal();
        User user = userMapper.selectByPrimaryKey(userMapper.selectUserIdByUsername(username));
        order.setUserId(user.getId());
        //获取购物车中的需要付款的信息
        CartExample cartExample = new CartExample();
        CartExample.Criteria criteria = cartExample.createCriteria();
        criteria.andUserIdEqualTo(user.getId());
        criteria.andCheckedEqualTo(true);
        criteria.andDeletedEqualTo(false);
        List<Cart> carts = cartMapper.selectByExample(cartExample);
        short number = (short) carts.size();
        order.setComments(number);
        orderMapper.updateByPrimaryKeySelective(order);
    }

    @Override
    /**
     * @author: huzhouming
     * @description: 获取需要评价的订单信息
     * @date: 2022/5/9
     * @param map
     * @return com.cskaoyan.model.OrderGoods
     */
    public OrderGoods selectUserGoods(Integer goodsId, Integer orderId) {
        OrderGoodsExample orderGoodsExample = new OrderGoodsExample();
        OrderGoodsExample.Criteria criteria = orderGoodsExample.createCriteria();
        criteria.andGoodsIdEqualTo(goodsId);
        criteria.andOrderIdEqualTo(orderId);
        List<OrderGoods> orderGoods = orderGoodsMapper.selectByExample(orderGoodsExample);
        return orderGoods.get(0);
    }

    @Override
    /**
     * @author: huzhouming
     * @description: 添加商品评论
     * @date: 2022/5/9
     * @param wxCommentBO
     * @return void
     */
    public void updateUserComment(WxOrderCommentBO wxOrderCommentBO) {
        //新建Comment对象进行添加
        OrderGoodsExample orderGoodsExample1 = new OrderGoodsExample();
        OrderGoodsExample.Criteria criteria1 = orderGoodsExample1.createCriteria();
        criteria1.andIdEqualTo(wxOrderCommentBO.getOrderGoodsId());
        List<OrderGoods> orderGoods1 = orderGoodsMapper.selectByExample(orderGoodsExample1);
        OrderGoods orderGoods2 = orderGoods1.get(0);
        Comment comment = new Comment();
        comment.setContent(wxOrderCommentBO.getContent());
        comment.setHasPicture(wxOrderCommentBO.getHasPicture());
        comment.setStar(wxOrderCommentBO.getStar());
        comment.setPicUrls(wxOrderCommentBO.getPicUrls());
        comment.setValueId(wxOrderCommentBO.getOrderGoodsId());
        comment.setAddTime(new Date());
        //拿到此时登录的用户Id
        Subject subject = SecurityUtils.getSubject();
        String username = (String) subject.getPrincipals().getPrimaryPrincipal();
        Integer userId = userMapper.selectUserIdByUsername(username);
        comment.setUserId(userId);
        //插入数据库
        commentMapper.insertSelective(comment);
        //修改OrderGoods数据库的comment值
        OrderGoodsExample orderGoodsExample = new OrderGoodsExample();
        OrderGoodsExample.Criteria criteria = orderGoodsExample.createCriteria();
        criteria.andIdEqualTo(wxOrderCommentBO.getOrderGoodsId());
        OrderGoods orderGoods = new OrderGoods();
        orderGoods.setComment(comment.getId());
        orderGoodsMapper.updateByExampleSelective(orderGoods, orderGoodsExample);
        //修改Order数据库的comment值
        orderMapper.updateCommentByGoodsId(orderGoods2.getOrderId());
    }

    @Override
    /**
     * @author: huzhouming
     * @description: TODO 通过购物车的sumbit生成新的order订单和order_goods
     * @date: 2022/5/10
     * @param wxSubmitBO
     * @return java.lang.Integer 返回生成订单的id
     */
    public Integer insertOrder(WxSubmitBO wxSubmitBO) {
        Order order = new Order();
        order.setMessage(wxSubmitBO.getMessage());
        //获取address信息
        Address address = addressMapper.selectByPrimaryKey(wxSubmitBO.getAddressId());
        //获取具体的省份和城市信息
        String orderAddress = null;
        Region region = regionMapper.selectByPrimaryKey(Integer.parseInt(address.getProvince()));
        Region region1 = regionMapper.selectByPrimaryKey(Integer.parseInt(address.getCity()));
        Region region2 = regionMapper.selectByPrimaryKey(Integer.parseInt(address.getCounty()));
        orderAddress = region.getName() + region1.getName() + region2.getName() + address.getAddressDetail();
        order.setAddress(orderAddress);
        order.setConsignee(address.getName());
        order.setMobile(address.getTel());
        order.setAftersaleStatus((short) 0);

        //获取当前用户信息
        Subject subject = SecurityUtils.getSubject();
        String username = (String) subject.getPrincipals().getPrimaryPrincipal();
        User user = userMapper.selectByPrimaryKey(userMapper.selectUserIdByUsername(username));
        order.setUserId(user.getId());
        //获取购物车中的需要付款的信息
        CartExample cartExample = new CartExample();
        CartExample.Criteria criteria = cartExample.createCriteria();
        criteria.andUserIdEqualTo(user.getId());
        criteria.andCheckedEqualTo(true);
        criteria.andDeletedEqualTo(false);
        List<Cart> carts = cartMapper.selectByExample(cartExample);
        Double goodsPrice = 0.0;
        for (Cart cart : carts) {
            goodsPrice += (cart.getNumber() * cart.getPrice());
            cart.setDeleted(true);
            cartMapper.updateByPrimaryKey(cart);
        }
        order.setGoodsPrice(new BigDecimal(goodsPrice));
        //获取配送费用信息
        SystemExample systemExample = new SystemExample();
        SystemExample.Criteria criteria1 = systemExample.createCriteria();
        criteria1.andKeyNameEqualTo("market_express_freight_min");
        List<System> list = systemMapper.selectByExample(systemExample);
        SystemExample systemExample1 = new SystemExample();
        SystemExample.Criteria criteria2 = systemExample1.createCriteria();
        criteria2.andKeyNameEqualTo("market_express_freight_value");
        List<System> list1 = systemMapper.selectByExample(systemExample1);
        //判断配送费是否满减
        if ((Integer.parseInt(list.get(0).getKeyValue()) > goodsPrice)) {
            //未满减
            order.setFreightPrice(new BigDecimal(Integer.parseInt(list1.get(0).getKeyValue())));
        } else {
            //满减
            order.setFreightPrice(new BigDecimal(0));
        }
        //优惠券部分
        if (wxSubmitBO.getUserCouponId() != 0) {
            CouponUser couponUser = couponUserMapper.selectByPrimaryKey(wxSubmitBO.getUserCouponId());
            //加入使用时间
            couponUser.setUpdateTime(new Date());
            //修改优惠券状态
            couponUser.setStatus((short) 1);
            //加入修改时间
            couponUser.setUpdateTime(new Date());
            couponUser.setId(null);
            CouponUserExample couponUserExample = new CouponUserExample();
            CouponUserExample.Criteria criteria3 = couponUserExample.createCriteria();
            criteria3.andIdEqualTo(wxSubmitBO.getUserCouponId());
            couponUserMapper.updateByExampleSelective(couponUser, couponUserExample);
            //获取优惠金额
            Coupon coupon = couponMapper.selectByPrimaryKey(wxSubmitBO.getCouponId());
            order.setCouponPrice(coupon.getDiscount());
        } else {
            //没有使用优惠券
            order.setCouponPrice(new BigDecimal(0));
        }
        //订单费用
        order.setOrderPrice(order.getGoodsPrice().add(order.getFreightPrice()).subtract(order.getCouponPrice()));
        order.setActualPrice(order.getOrderPrice());
        //订单创建时间
        order.setAddTime(new Date());
        //生成订单编号 = 下单时间 + userid + 手机号前三位
        SimpleDateFormat sdf = new SimpleDateFormat("yyyyMMddHHmmss");
        String format = sdf.format(new Date());
        order.setOrderSn(format + Integer.toString(order.getUserId()) + format.substring(0, 3));
        order.setOrderStatus((short) 101);
        order.setIntegralPrice(new BigDecimal(0));
        order.setGrouponPrice(new BigDecimal(0));
        order.setComments((short) 0);
        order.setDeleted(false);
        orderMapper.insert(order);
        //以上订单生成完毕，以下看是生成order_goods
        for (Cart cart : carts) {
            orderGoodsMapper.insertSelective(new OrderGoods(order.getId(), cart));
        }
        return order.getId();
    }

    @Override
    /**
     * @author: huzhouming
     * @description: TODO 付钱
     * @date: 2022/5/11
     * @param orderId
     * @return int
     */
    public int updatePrepay(Map map, HttpSession session) {

        String id = String.valueOf(map.get("orderId"));
        if (session.getAttribute("orderId" + id) != null) {
            OrderExample orderExample = new OrderExample();
            OrderExample.Criteria criteria = orderExample.createCriteria();
            criteria.andIdEqualTo(Integer.parseInt((String) map.get("orderId")));
            Order order = new Order();
            order.setPayTime(new Date());
            order.setOrderStatus((short) 201);
            orderMapper.updateByExampleSelective(order, orderExample);
            return 1;
        }
        session.setAttribute("orderId" + id, "1111");
        return 0;
    }
}
